package com.avit.tv.kui;

import android.content.Context;
import android.content.res.TypedArray;
import android.graphics.*;
import android.os.Handler;
import android.os.Message;
import android.text.TextPaint;
import android.text.TextUtils;
import android.util.AttributeSet;
import android.view.KeyEvent;
import androidx.annotation.ColorInt;
import androidx.annotation.NonNull;
import androidx.annotation.Nullable;
import com.avit.tv.kui.base.BaseFocusLayout;
import com.avit.tv.kui.progressbar.*;
import com.avit.tv.kui.utils.Log;
import com.avit.tv.kui.utils.TimeUtils;
import com.avit.tv.kui.utils.Utils;

import java.lang.ref.WeakReference;
import java.util.ArrayList;
import java.util.List;
import java.util.Map;
import java.util.Set;

/**
 * 进度条或者选择项
 *
 * @author like
 * @date 2020/7/8
 */
public class AvitProgressbar extends BaseFocusLayout {
    private int defaultColor;
    private int defaultHeight;
    private int progressColor;
    private int progressHeight;
    private boolean isNeedShowPoint;

    private Paint timeFlagTextPaint;

    /**
     * 绘制整个布局的进度画笔
     */
    private Path defaultPath;
    private Paint defaultPaint;
    /**
     * 绘制进度条进度画笔
     */
    private Path progressPath;
    private Paint progressPaint;

    /**
     * 关键点path
     */
    private Path currentPointPath;
    private Paint currentPointPaint;

    /**
     * 绘制当前的flag
     */
    private Paint currentFlagPaint;
    private Path currentFlagPath;

    /**
     * 绘制关键点
     */
    private Paint pointPaint;
    private Path pointPath;

    /**
     * 绘制关键条目框
     */
    private Path pointLinePath;
    private Paint pointLinePaint;

    /**
     * 绘制时间进度
     */
    private Path timeFlagPath;
    private Paint timeFlagPaint;
    private Paint timeClockPaint;

    /**
     * 绘制移动显示的 line
     */
    private Path dertaCurrentPath;
    private Paint dertaCurrentPaint;

    /**
     * 具体的此view 显示的盒子布局
     */
    private RectF showRec;

    private float baseLineY;

    private float startX;

    /**
     * 分因子，用于屏幕适配
     */
    private int radix;

    /**
     * 适配器
     */
    private ProgressbarAdapter adapter;

    /**
     * 每次progress滚动的长度
     */
    private float percentMoveWidth;

    /**
     * 滚动标记
     */
    private float totalWidth;

    /**
     * seekbar高度
     */
    private float viewWidth;

    /**
     * 移动倍数
     */
    private int progressMoveMultiple;

    /**
     * 标记点颜色
     */
    @ColorInt
    private int pointColor;

    /**
     * 标记点的颜色
     */
    private int pointFlagColor;

    /**
     * 标记物的高度
     */
    private int pointFlagHeight;

    /**
     * 标记物的宽度
     */
    private int pointFlagWidth;

    /**
     * 当前进度绘制的text
     */
    private Paint currentFlagTextPaint;


    /**
     * 是否默认向右侧显示
     */
    private boolean isCurrentTagDefault;

    /**
     * 当前进度下绘制的文本颜色
     */
    @ColorInt
    private int currentFlagTextColor;

    /**
     * 当前显示的text 大小
     */
    private int currentFlagTextSize;

    /**
     * 当前进度flag 的颜色
     */
    @ColorInt
    private int currentFlagColor;

    /**
     * 当前进度flag 文本信息
     */
    private String currentFlagValue;

    /**
     * 当前 时间
     */
    private long currentTime;

    /**
     * 绘制关键点的文字
     *
     * @return
     */
    private Paint pointFlagTextPaint;

    /**
     * 关键点的标签上的文字颜色
     */
    private int pointFlagTextColor;

    /**
     * 关键点的标签上的文字大小
     */
    private int pointFlagTextSize;


    /**
     * 触发移动的 handler
     */
    private final ProgressHandler moveHandler = new ProgressHandler(new WeakReference<>(this));

    /**
     * 底部绘制框
     */
    private RectF pointFlagRect;

    /**
     * 进度条对外的监听
     */
    private ProgressListener listener;

    /**
     * 进度条下方显示文字的bar
     */
    private ProgressTagBar progressTagbar;

    /**
     * 关键点的划线颜色
     */
    private int pointLineColor;

    /**
     * 是否第一次渲染
     */
    private boolean isFirst;

    /**
     * 判断子点所在的 TextView 的集合
     */
    private List<ImportPointValue> resultValues;

    /**
     * 显示标尺的上半部分的计算显示区域
     */
    private RectF timeFlagRect;

    /**
     * 控制左右滑动中线的大小
     */
    private int dertaLineSize;

    /**
     * 控制左右滑动中线的颜色
     */
    @ColorInt
    private int dertaLineColor;

    /**
     * 按下按键的时候锚点线长度
     */
    private float progressStartX;

    /**
     * 是否在用户操作滑动
     */
    private boolean isOnProgress;

    /**
     * 是否开启时间刻度
     */
    private boolean isOpenClock;

    /**
     * 控制进度条过后的回调
     */
    private SeekListener seekListener;

    /**
     * 中间对比点
     */
    private ImportPointValue tempSwapValue;

    public AvitProgressbar(@NonNull Context context) {
        super(context);
    }

    public AvitProgressbar(@NonNull Context context, @Nullable AttributeSet attrs) {
        super(context, attrs);
    }

    public AvitProgressbar(@NonNull Context context, @Nullable AttributeSet attrs, int defStyleAttr) {
        super(context, attrs, defStyleAttr);
    }

    @Override
    protected void initView(Context context, AttributeSet attrs, int defStyleAttr) {
        radix = Utils.getRadix(context);
        int DEFAULT_HEIGHT = radix * 5;
        progressMoveMultiple = 1;
        TypedArray typedArray = context.obtainStyledAttributes(attrs,
                R.styleable.AvitProgressbar, defStyleAttr, 0);
        defaultColor = typedArray.getColor(R.styleable.AvitProgressbar_default_color, Color.LTGRAY);
        defaultHeight = typedArray.getDimensionPixelSize(R.styleable.AvitProgressbar_default_height, DEFAULT_HEIGHT);
        progressColor = typedArray.getColor(R.styleable.AvitProgressbar_progress_color, Color.WHITE);
        progressHeight = typedArray.getDimensionPixelSize(R.styleable.AvitProgressbar_progress_height, DEFAULT_HEIGHT);
        isNeedShowPoint = typedArray.getBoolean(R.styleable.AvitProgressbar_is_need_show_point, false);
        currentFlagColor = typedArray.getColor(R.styleable.AvitProgressbar_current_flag_color, Color.DKGRAY);
        currentFlagValue = typedArray.getString(R.styleable.AvitProgressbar_current_flag_text_value);
        currentFlagTextColor = typedArray.getColor(R.styleable.AvitProgressbar_current_flag_text_color, Color.WHITE);
        currentFlagTextSize = typedArray.getDimensionPixelSize(R.styleable.AvitProgressbar_current_flag_text_size, defaultHeight * 2);
        pointColor = typedArray.getColor(R.styleable.AvitProgressbar_point_color, Color.WHITE);
        pointLineColor = typedArray.getColor(R.styleable.AvitProgressbar_point_flag_line_color, Color.LTGRAY);
        pointFlagColor = typedArray.getColor(R.styleable.AvitProgressbar_point_flag_color, Color.DKGRAY);
        pointFlagTextColor = typedArray.getColor(R.styleable.AvitProgressbar_point_flag_text_color, Color.WHITE);
        pointFlagTextSize = typedArray.getDimensionPixelSize(R.styleable.AvitProgressbar_point_flag_text_size, defaultHeight * 2);
        dertaLineSize = typedArray.getDimensionPixelSize(R.styleable.AvitProgressbar_derta_line_size, DEFAULT_HEIGHT);
        dertaLineColor = typedArray.getColor(R.styleable.AvitProgressbar_derta_line_color, Color.RED);
        pointFlagHeight = defaultHeight * 9;
        pointFlagWidth = defaultHeight * 16;
        typedArray.recycle();
        if (isNeedShowPoint)
            setMinimumHeight(27 * defaultHeight);
        else
            setMinimumHeight(defaultHeight * 18);
        if (TextUtils.isEmpty(currentFlagValue))
            currentFlagValue = context.getString(R.string.current_flag_default_value);
        isFirst = true;
    }

    @Override
    protected void initContent(Context context) {
        defaultPath = new Path();
        defaultPaint = new Paint(Paint.ANTI_ALIAS_FLAG);

        progressPath = new Path();
        progressPaint = new Paint(Paint.ANTI_ALIAS_FLAG);

        currentPointPath = new Path();
        currentPointPaint = new Paint(Paint.ANTI_ALIAS_FLAG);

        pointPath = new Path();
        pointPaint = new Paint(Paint.ANTI_ALIAS_FLAG);

        currentFlagPath = new Path();
        currentFlagPaint = new Paint(Paint.ANTI_ALIAS_FLAG);

        pointLinePath = new Path();
        pointLinePaint = new Paint(Paint.ANTI_ALIAS_FLAG);

        dertaCurrentPath = new Path();
        dertaCurrentPaint = new Paint(Paint.ANTI_ALIAS_FLAG);

        timeFlagPath = new Path();
        timeFlagPaint = new Paint(Paint.ANTI_ALIAS_FLAG);
        timeClockPaint = new Paint(Paint.ANTI_ALIAS_FLAG);

        currentFlagTextPaint = new TextPaint(Paint.ANTI_ALIAS_FLAG);
        timeFlagTextPaint = new TextPaint(Paint.ANTI_ALIAS_FLAG);
        pointFlagTextPaint = new TextPaint(Paint.ANTI_ALIAS_FLAG);

        showRec = new RectF();
        progressTagbar = new ProgressTagBar(context);
        resultValues = new ArrayList<>();

        defaultPaint.setStyle(Paint.Style.STROKE);
        defaultPaint.setColor(defaultColor);
        defaultPaint.setPathEffect(new CornerPathEffect(defaultHeight));
        defaultPaint.setStrokeWidth(defaultHeight);

        currentPointPaint.setStyle(Paint.Style.FILL);
        currentPointPaint.setColor(progressColor);

        pointPaint.setStyle(Paint.Style.STROKE);
        pointPaint.setColor(pointColor);
        pointPaint.setStrokeWidth(radix);

        progressPaint.setStyle(Paint.Style.STROKE);
        progressPaint.setPathEffect(new CornerPathEffect(progressHeight));
        progressPaint.setColor(progressColor);
        progressPaint.setStrokeWidth(progressHeight);

        currentFlagPaint.setStyle(Paint.Style.FILL_AND_STROKE);
        currentFlagPaint.setColor(currentFlagColor);
        currentFlagPaint.setPathEffect(new CornerPathEffect(progressHeight));
        currentFlagPaint.setStrokeWidth(radix);

        pointLinePaint.setStyle(Paint.Style.STROKE);
        pointLinePaint.setColor(pointLineColor);
        pointLinePaint.setStrokeWidth(radix);

        timeFlagPaint.setStyle(Paint.Style.FILL_AND_STROKE);
        timeFlagPaint.setColor(pointFlagColor);
        timeFlagPaint.setStrokeWidth(radix);

        timeClockPaint.setStyle(Paint.Style.STROKE);
        timeClockPaint.setColor(currentFlagTextColor);
        timeClockPaint.setStrokeWidth(radix);

        dertaCurrentPaint.setStyle(Paint.Style.STROKE);
        dertaCurrentPaint.setColor(dertaLineColor);
        dertaCurrentPaint.setStrokeWidth(dertaLineSize);
        dertaCurrentPaint.setPathEffect(new CornerPathEffect(progressHeight));

        currentFlagTextPaint.setColor(currentFlagTextColor);
        currentFlagTextPaint.setTextSize(currentFlagTextSize);
        currentFlagTextPaint.setTextAlign(Paint.Align.CENTER);

        timeFlagTextPaint.setColor(currentFlagTextColor);
        timeFlagTextPaint.setTextSize(currentFlagTextSize);
        timeFlagTextPaint.setTextAlign(Paint.Align.CENTER);

        pointFlagTextPaint.setColor(pointFlagTextColor);
        pointFlagTextPaint.setTextSize(pointFlagTextSize);
        pointFlagTextPaint.setTextAlign(Paint.Align.CENTER);


    }

    @Override
    protected void insertView() {
    }

    @Override
    protected void dispatchDraw(Canvas canvas) {
        super.dispatchDraw(canvas);
        if (adapter == null) return;
        if (isFirst) {
            initBaseSome();
            initPointFlag();
            initUserProgress();
            isFirst = false;
        }
        initTotalWidth();
        drawDefault(canvas);
//      drawCurrentFlag(canvas);
        drawDertaMidLine(canvas);
        drawMoveProgress(canvas);
        canvas.drawPath(currentPointPath, currentPointPaint);
        canvas.save();
        canvas.restore();
    }

    private void initTotalWidth(){
        totalWidth = adapter.getTotalWidth(currentTime, viewWidth - startX);
        if (!isOnProgress){
            progressStartX = totalWidth;
        }
    }

    /**
     * 更新底部布局
     */
    private void initPointFlag() {
        progressTagbar.setX(pointFlagRect.left);
        progressTagbar.setY(baseLineY);
        progressTagbar.setMinimumWidth(Math.round(pointFlagRect.right - pointFlagRect.left));
        progressTagbar.setMinimumHeight(Math.round(pointFlagRect.bottom - pointFlagRect.top));
        progressTagbar.setTextColor(pointFlagTextColor);
        progressTagbar.setDrawableColor(pointFlagColor);
        progressTagbar.setTextSize(pointFlagTextSize);
        List<ImportPointValue> importantPoints = adapter.getImportantPoints ();
        if (importantPoints!=null)
            progressTagbar.initTextValues(importantPoints, Math.round(viewWidth));
        LayoutParams layoutParams = new LayoutParams(LayoutParams.WRAP_CONTENT, LayoutParams.WRAP_CONTENT);
        addView(progressTagbar, layoutParams);
    }


    /**
     * init baseLine
     */
    private void initBaseSome() {
        baseLineY = Math.abs(showRec.bottom - showRec.top) / 2 ;
        startX = getX() + defaultHeight;
        viewWidth = Math.abs(showRec.left - showRec.right) - startX;
        pointFlagRect = new RectF(0, baseLineY , showRec.right, baseLineY + pointFlagHeight*2/3f);
        timeFlagRect = new RectF(0, baseLineY- pointFlagHeight*2/3f , showRec.right, baseLineY );
        percentMoveWidth = adapter.initPercentMoveWidth(viewWidth - startX);
    }


    /**
     * 绘制时间刻度尺
     * @param canvas
     */
    private void drawTimeClock(Canvas canvas){
        timeFlagPath.reset();
        Map<Long, Float> clockWidth = adapter.getClockWidth(percentMoveWidth);
        if (clockWidth.isEmpty())return;
        Set<Long> times = clockWidth.keySet();
        float y = baseLineY - pointFlagTextSize;
        for (long time: times){
            float dertaX = clockWidth.get(time);
            canvas.drawText(TimeUtils.getTimeMin(time), startX+dertaX, y ,timeFlagTextPaint );
            timeFlagPath.moveTo(startX+dertaX, baseLineY);
            timeFlagPath.lineTo(startX+dertaX, baseLineY - 2*pointFlagTextSize/3f);
        }
        timeFlagPath.close();
        canvas.drawPath(timeFlagPath, timeClockPaint);
    }


    /**
     * init 重点帧的点
     * # 注释为算法点，为保留算法定点，不要删掉
     */
    private void initImportPoint(Canvas canvas) {
        pointPath.reset();
        pointLinePath.reset();
        resultValues.clear();
        List<ImportPointValue> values = adapter.getFinalPointX(percentMoveWidth);
        for (ImportPointValue value : values
        ) {
            if (value.getShowX() < viewWidth && value.getShowX() > startX) {
//                pointPath.addCircle(startX+value.getShowX(), baseLineY, progressHeight, Path.Direction.CW);
                if (isOpenClock)
                    pointLinePath.moveTo(startX + value.getShowX(), baseLineY - defaultHeight / 2f);
                else {
                    drawPointTime(value, canvas);
                    pointLinePath.moveTo(startX + value.getShowX(), baseLineY - 1.5f * defaultHeight);
                }
                pointLinePath.lineTo(startX+value.getShowX(), baseLineY+pointFlagHeight/3f);
                value.setTagTextX(startX+value.getShowX());
                resultValues.add(value);
            }
            if (adapter.isShowStartText(value.getPointEndTime(), value.getPointStartTime())){
                resultValues.add(value);
                value.setTagTextX(startX);
            }
        }
        progressTagbar.setPoints(resultValues);
        pointPath.close();
        pointLinePath.close();
        canvas.drawPath(pointLinePath, pointLinePaint);
    }

    /**
     * 绘制关键点的时间
     * @param value
     * @param canvas
     */
    private void drawPointTime(ImportPointValue value, Canvas canvas){
        String timeMin = TimeUtils.getTimeMin(value.getPointStartTime());
        float textWidth = pointFlagTextPaint.measureText(timeMin);
        float x = startX + value.getShowX();
        if (tempSwapValue!=null) {
            float tempX= startX + tempSwapValue.getShowX();
            if (Math.abs(x - tempX)<textWidth)
                x += textWidth/2f;
        }
        float y = baseLineY - pointFlagTextSize;
        tempSwapValue = value;
        canvas.drawText(TimeUtils.getTimeMin(value.getPointStartTime()), x, y, pointFlagTextPaint);
    }

    /**
     * 绘制基本默认背景
     *
     * @param canvas
     */
    private void drawDefault(Canvas canvas) {
        defaultPath.reset();
        defaultPath.moveTo(startX, baseLineY);
        defaultPath.lineTo(viewWidth, baseLineY);
        defaultPath.close();
        canvas.drawRect(timeFlagRect, timeFlagPaint);
        canvas.drawPath(defaultPath, defaultPaint);
        float measureText = timeFlagTextPaint.measureText(TimeUtils.getTimeMin(adapter.getStartTimeSec()));
        float textBaseLineY = Math.abs(timeFlagTextPaint.ascent() + timeFlagTextPaint.descent()) / 2;
        canvas.drawText(TimeUtils.getTimeMin(adapter.getStartTimeSec()), startX-measureText*2/3, baseLineY+textBaseLineY , timeFlagTextPaint);
        canvas.drawText(TimeUtils.getTimeMin(adapter.getEndTimeSec()), viewWidth+measureText/2+currentFlagTextSize/2f, baseLineY+textBaseLineY  , timeFlagTextPaint);
        canvas.save();
    }

    /**
     * 更新绘制进度
     *
     * @param canvas
     */
    private void drawMoveProgress(Canvas canvas) {
        progressPath.reset();
        currentPointPath.reset();
        currentPointPath.addCircle(startX + totalWidth, baseLineY, progressHeight, Path.Direction.CW);
//        progressPath.moveTo(startX + totalWidth, baseLineY);
//        progressPath.lineTo(startX, baseLineY);
        if (isNeedShowPoint){
            if (isOpenClock)
                drawTimeClock(canvas);
            initImportPoint(canvas);
        }else {
            drawCurrentText(canvas);
        }
        progressPath.close();
        currentPointPath.close();
        canvas.drawPath(progressPath, progressPaint);
        canvas.drawPath(pointPath, pointPaint);
        canvas.save();
    }

    /**
     * 绘制当前进度时间
     * @param canvas
     */
    private void drawCurrentText(Canvas canvas) {
        float x = startX + totalWidth;
        float y = baseLineY - pointFlagTextSize;
        canvas.drawText(TimeUtils.getTimeSec(currentTime), x, y, currentFlagTextPaint);
        canvas.save();
    }

    /**
     * 绘制当前的进度标志
     *
     * @param canvas
     */
    private void drawCurrentFlag(Canvas canvas) {
        currentFlagPath.reset();
        currentFlagPath.moveTo(startX + totalWidth, baseLineY);
        currentFlagPath.lineTo(startX + totalWidth, baseLineY - pointFlagHeight);
        if (startX + totalWidth + pointFlagWidth > viewWidth)
            isCurrentTagDefault = false;
        if (startX + totalWidth - pointFlagWidth < 0)
            isCurrentTagDefault = true;
        float right = isCurrentTagDefault ? startX + totalWidth + pointFlagWidth : startX + totalWidth - pointFlagWidth;
        currentFlagPath.addRect(new RectF(startX + totalWidth, baseLineY - pointFlagHeight / 3f, right,
                baseLineY - pointFlagHeight * 1.2f), Path.Direction.CCW);
        float x = (right + startX + totalWidth) / 2;
        float y = baseLineY + pointFlagHeight * (1 / 3f - 2) / 2;
        currentFlagPath.close();
        canvas.drawPath(currentFlagPath, currentFlagPaint);
        canvas.drawText(TimeUtils.getTimeSec(currentTime), x, y, currentFlagTextPaint);
        canvas.drawText(currentFlagValue, x, y + currentFlagTextSize, currentFlagTextPaint);
        canvas.save();
    }


    /**
     * 绘制手动滑动的中线
     * @param canvas
     */
    private void drawDertaMidLine(Canvas canvas){
        dertaCurrentPath.reset();
        dertaCurrentPath.moveTo(startX+progressStartX, baseLineY);
        dertaCurrentPath.lineTo(startX, baseLineY);
        dertaCurrentPath.close();
        canvas.drawPath(dertaCurrentPath,dertaCurrentPaint);
    }

    /**
     * 进度增加
     * @param isUserProgress 是否是用户拖动进度条
     * @return
     */
    private boolean progressUp(boolean isUserProgress) {
        boolean state = false;
        if (progressMoveMultiple <= 10 && isUserProgress)
            progressMoveMultiple += 1;
        if (totalWidth + startX < viewWidth) {
            currentTime += progressMoveMultiple;
            state = true;
        } else if (!isUserProgress && isNeedShowPoint) {
            currentTime += progressMoveMultiple;
        }
        if (currentTime > adapter.getEndTimeSec()) {
            currentTime = adapter.getEndTimeSec();
            state = false;
        }
        if (!isUserProgress)
            progressStartX = totalWidth;
        return state;
    }

    /**
     * 进度减小
     */
    private void progressDown() {
        if (progressMoveMultiple <= 10)
            progressMoveMultiple += 1;
        if (totalWidth > 0) {
            currentTime -= progressMoveMultiple;
        }
        if (currentTime < adapter.getStartTimeSec())
            currentTime = adapter.getStartTimeSec();
    }

    @Override
    protected void onLayout(boolean changed, int left, int top, int right, int bottom) {
        super.onLayout(changed, left, top, right, bottom);
        showRec.left = left;
        showRec.bottom = bottom;
        showRec.right = right;
        showRec.top = top;
    }

    /**
     * 更新用户按键的时候参数
     */
    private void initUserProgress(){
        if (progressStartX == 0)
            progressStartX = totalWidth;
    }

    @Override
    public boolean dispatchKeyEvent(KeyEvent event) {
        if (KeyEvent.ACTION_DOWN == event.getAction()) {
            switch (event.getKeyCode()) {
                case KeyEvent.KEYCODE_DPAD_LEFT:
                    initSeekTo(true);
                    progressDown();
                    pauseProgress();
                    invalidate();
                    break;
                case KeyEvent.KEYCODE_DPAD_RIGHT:
                    initSeekTo(false);
                    progressUp(true);
                    pauseProgress();
                    invalidate();
                    break;
            }
        } else if (event.getAction() == KeyEvent.ACTION_UP) {
            progressMoveMultiple = 1;
            switch (event.getKeyCode()) {
                case KeyEvent.KEYCODE_DPAD_LEFT:
                case KeyEvent.KEYCODE_DPAD_RIGHT:
                    if (seekListener!=null){
                        seekListener.onSeeked(currentTime);
                    }
                    isOnProgress = false;
                    invalidate();
                    break;
            }
        }
        return super.dispatchKeyEvent(event);
    }


    private void initSeekTo(boolean isLeftSeek){
        if (seekListener!=null&&!isOnProgress){
            seekListener.onStartSeek(currentTime, isLeftSeek);
            isOnProgress = true;
        }
    }

    /**
     * 设置默认进度条颜色
     *
     * @param defaultColor
     */
    public void setDefaultColor(int defaultColor) {
        this.defaultColor = defaultColor;
        defaultPaint.setColor(defaultColor);
    }

    /**
     * 设置默认进度条高度
     *
     * @param defaultHeight
     */
    public void setDefaultHeight(int defaultHeight) {
        this.defaultHeight = defaultHeight;
        defaultPaint.setStrokeWidth(defaultHeight);
    }

    /**
     * 设置 progress 进度条的颜色
     *
     * @param progressColor
     */
    public void setProgressColor(int progressColor) {
        this.progressColor = progressColor;
        progressPaint.setColor(progressColor);
    }

    /**
     * 设置progress 进度条高度
     *
     * @param progressHeight
     */
    public void setProgressHeight(int progressHeight) {
        this.progressHeight = progressHeight;
        progressPaint.setStrokeWidth(progressHeight);
    }

    /**
     * 设置当前进度的 flag 上文字下方的文本
     *
     * @param currentFlagValue
     */
    public void setCurrentFlagValue(String currentFlagValue) {
        this.currentFlagValue = currentFlagValue;
        invalidate();
    }

    /**
     * 是否显示关键帧的点
     *
     * @param needShowPoint
     */
    public void setNeedShowPoint(boolean needShowPoint) {
        isNeedShowPoint = needShowPoint;
        invalidate();
    }

    /**
     * 获取适配器
     *
     * @param adapter
     */
    public void setAdapter(ProgressbarAdapter adapter) {
        this.adapter = adapter;
        currentTime = adapter.getStartTimeSec();
        invalidate();
    }

    /**
     * 设置当前时间 单位秒
     *
     * @param sec 时间 [单位：秒]
     */
    public void setCurrentProgress(long sec) {
        currentTime = sec;
        invalidate();
    }

    /**
     * 设置底部默认背景的颜色，默认布局显示为带有弧形框
     *
     * @param pointFlagColor
     */
    public void setPointFlagColor(@ColorInt int pointFlagColor) {
        this.pointFlagColor = pointFlagColor;
        progressTagbar.setDrawableColor(pointFlagColor);
        timeFlagPaint.setColor(pointFlagColor);

    }

    /**
     * 设置关键点标签文字颜色
     *
     * @param pointFlagTextColor
     */
    public void setPointFlagTextColor(@ColorInt int pointFlagTextColor) {
        this.pointFlagTextColor = pointFlagTextColor;
        pointFlagTextPaint.setColor(pointFlagTextColor);
        progressTagbar.setTextColor(pointFlagTextColor);
    }

    /**
     * 设置关键点标签文字尺寸
     *
     * @param pointFlagTextSize
     */
    public void setPointFlagTextSize(int pointFlagTextSize) {
        this.pointFlagTextSize = pointFlagTextSize;
        pointFlagTextPaint.setTextSize(pointFlagTextSize);
        progressTagbar.setTextSize(pointFlagTextSize);
    }

    /**
     * 设置当前时间点标签颜色
     *
     * @param currentFlagColor
     */
    public void setCurrentFlagColor(@ColorInt int currentFlagColor) {
        this.currentFlagColor = currentFlagColor;
        currentFlagPaint.setColor(currentFlagColor);
    }

    /**
     * 设置当前时间点标签文字颜色
     *
     * @param currentFlagTextColor
     */
    public void setCurrentFlagTextColor(@ColorInt int currentFlagTextColor) {
        this.currentFlagTextColor = currentFlagTextColor;
        currentFlagTextPaint.setColor(currentFlagTextColor);
    }

    /**
     * 设置当前时间点标签文字大小
     *
     * @param currentFlagTextSize
     */
    public void setCurrentFlagTextSize(int currentFlagTextSize) {
        this.currentFlagTextSize = currentFlagTextSize;
        currentFlagTextPaint.setTextSize(currentFlagTextSize);
    }

    /**
     * 设置划线颜色
     * @param pointLineColor
     */
    public void setPointLineColor(@ColorInt int pointLineColor) {
        this.pointLineColor = pointLineColor;
        pointLinePaint.setColor(pointLineColor);
    }

    /**
     * 获取对外监听
     *
     * @param listener
     */
    public void setListener(ProgressListener listener) {
        this.listener = listener;
    }

    /**
     * 开启滚动
     */
    public void startProgress() {
        moveHandler.sendEmptyMessage(ProgressStates.STATE_START);
    }

    /**
     * 暂停滚动
     */
    public void pauseProgress() {
        moveHandler.sendEmptyMessage(ProgressStates.STATE_PAUSE);
    }

    /**
     * 继续滚动
     */
    public void progressContinue() {
        moveHandler.execute();
    }



    /**
     * 进度条状态
     */
    public static final class ProgressStates {
        public static final int STATE_START = 0X0000;
        public static final int STATE_PROGRESSING = 0X0001;
        public static final int STATE_PAUSE = 0X1001;
        public static final int STATE_FINISH = 0X000F;
    }


    /**
     * 控制j进度条状态
     */
    private static final class ProgressHandler extends Handler {

        private WeakReference<AvitProgressbar> weakReference;

        public ProgressHandler(WeakReference<AvitProgressbar> weakReference) {
            this.weakReference = weakReference;
        }

        @Override
        public void handleMessage(Message msg) {
            super.handleMessage(msg);
            if (checkWeak()) {
                AvitProgressbar weakObj = weakReference.get();
                switch (msg.what) {
                    case ProgressStates.STATE_PROGRESSING:
                        Log.i(this, "state progressing:" + weakObj.currentTime);
                        if (weakObj.progressUp(false)) {
                            if (isListenerIsNotNull())
                                weakObj.listener.onProgress(weakObj.currentTime);
                            weakObj.invalidate();
                            executeDelay();
                        } else {
                            if (weakObj.isNeedShowPoint) {
                                weakObj.invalidate();
                                executeDelay();
                            } else
                                sendEmptyMessage(ProgressStates.STATE_FINISH);
                        }
                        break;
                    case ProgressStates.STATE_START:
                        Log.i(this, "state start: " +  weakObj.currentTime);
                        if (isListenerIsNotNull())
                            weakObj.listener.onPreStart();
                        weakObj.progressMoveMultiple = 1;
                        if (weakObj.isNeedShowPoint)
                            weakObj.currentTime = weakObj.adapter.getEndTimeSec();
                        else
                            weakObj.currentTime = weakObj.adapter.getStartTimeSec();
                        weakObj.totalWidth = weakObj.adapter.getTotalWidth(weakObj.currentTime, weakObj.viewWidth - weakObj.startX);
                        execute();
                        break;
                    case ProgressStates.STATE_PAUSE:
                        Log.i(this, "state pause: " +  weakObj.currentTime);
                        if (isListenerIsNotNull())
                            weakObj.listener.onPause();
                        removeMessages(ProgressStates.STATE_PROGRESSING);
                        break;
                    case ProgressStates.STATE_FINISH:
                        Log.i(this, "state finish: " +  weakObj.currentTime);
                        if (isListenerIsNotNull())
                            weakObj.listener.onFinish();
                        removeMessages(msg.what);
                        break;

                }
            } else
                release();
        }

        public void executeDelay() {
            removeMessages(ProgressStates.STATE_PROGRESSING);
            sendEmptyMessageDelayed(ProgressStates.STATE_PROGRESSING, 1000L);
        }

        public void execute() {
            removeMessages(ProgressStates.STATE_PROGRESSING);
            sendEmptyMessage(ProgressStates.STATE_PROGRESSING);
        }

        private boolean checkWeak() {
            return weakReference != null && weakReference.get() != null;
        }

        private void release() {
            removeCallbacksAndMessages(null);
        }

        private boolean isListenerIsNotNull() {
            return weakReference.get().listener != null;
        }
    }

    @Override
    protected void onDetachedFromWindow() {
        super.onDetachedFromWindow();
        if (moveHandler != null)
            moveHandler.release();
    }

    /**
     * 防止此layout 重绘导致资源频繁调用的问题
     *
     * @return
     */
    @Override
    public boolean isLayoutRequested() {
        return true;
    }

    /**
     * 获取当前进度条的适配器
     * @return
     */
    public ProgressbarAdapter getAdapter() {
        return adapter;
    }

    /**
     * 获取当前的进度
     * @return
     */
    public long getCurrentTime() {
        return currentTime;
    }

    /**
     * 是否开启后门
     * @return
     */
    public boolean isOpenClock() {
        return isOpenClock;
    }

    /**
     * 设置后门开启
     * @param openClock
     */
    public void setOpenClock(boolean openClock) {
        isOpenClock = openClock;
        invalidate();
    }

    public void setSeekListener(SeekListener seekListener) {
        this.seekListener = seekListener;
    }
}
